package megacli

import "fmt"

// RAID level
type Level string

// RAID levels
const (
    Unknown Level = "unknown"
    RAID0   Level = "RAID 0"
    RAID1   Level = "RAID 1"
    RAID5   Level = "RAID 5"
    RAID6   Level = "RAID 6"
    RAID01  Level = "RAID 0+1"
    RAID10  Level = "RAID 1+0"
)

// base number
type Base float64

// These are base numbers
const (
    Decimal Base = 1000.0
    Binary  Base = 1024.0
)

var pathList = []string{
    "/usr/bin/MegaCli",
    "/usr/bin/MegaCli64",
    "/usr/sbin/MegaCli",
    "/usr/sbin/MegaCli64",
    "/opt/MegaRAID/MegaCli/MegaCli",
    "/opt/MegaRAID/MegaCli/MegaCli64",
}

var clipath string

func init() {
    clipath, _ = scanPathList(pathList)
}

func Available() bool {
    if clipath == "" {
        return false
    }
    return true
}

// Decode makes Adapter satisfy the mox.Decoder interface
func (c *Controller) Decode() error {
    err := GetAdpInfo(c)
    if err != nil {
        return err
    }

    lds, err := GetLDList(c.Number)
    if err != nil {
        return err
    }

    ldmap := make(map[uint]*LogDrive)
    for _, ld := range lds {
        if _, ok := ldmap[ld.GroupID]; ok {
            return fmt.Errorf("duplicate group id found: %d", ld.GroupID)
        }

        ldmap[ld.GroupID] = ld
    }

    c.LogDrives = lds
    c.logDeriveMap = ldmap

    // scan unconfigured drives
    apd, err := GetAllPD(c.Number)
    if err != nil {
        return err
    }
    if len(apd) == 0 {
        return nil
    }

    wwnmap := make(map[string]bool)
    inqmap := make(map[string]bool)
    for _, ld := range c.LogDrives {
        for _, pd := range ld.PhyDrives {
            if pd.WWN != "" {
                wwnmap[pd.WWN] = true
            }

            if pd.InquiryRaw != "" {
                inqmap[pd.InquiryRaw] = true
            }
        }
    }

    for _, pd := range apd {
        if wwnmap[pd.WWN] { // means 'this drive is under a logical drive'
            continue
        }

        // means 'this drive is under a logical drive'
        // same SSD does not return WWN
        if inqmap[pd.InquiryRaw] {
            continue
        }
    }

    return nil
}